package cn.iftrue.japidemo.controller;

import cn.hutool.core.date.DateField;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.RandomUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.crypto.SecureUtil;
import cn.iftrue.japidemo.common.ApiErrorCode;
import cn.iftrue.japidemo.common.ApiResult;
import cn.iftrue.japidemo.system.entity.SysUser;
import cn.iftrue.japidemo.system.service.SysUserService;
import com.auth0.jwt.JWT;
import com.auth0.jwt.algorithms.Algorithm;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.List;

@RequestMapping("/users")
@RestController
public class UserController {
    @Resource
    private SysUserService sysUserService;
    @Value("${project.jwt.secret}")
    private String jwt_secret;

    @PostMapping("/token")
    public ApiResult login(SysUser sysUser){
        if(null==sysUser){
            return ApiResult.error(ApiErrorCode.A0400);
        }
        if(StrUtil.hasBlank(sysUser.getUserName(),sysUser.getPwd())){
            return ApiResult.error(ApiErrorCode.A0402);
        }
        LambdaQueryWrapper<SysUser> userLambdaQueryWrapper=new LambdaQueryWrapper<>();
        userLambdaQueryWrapper.eq(SysUser::getUserName,sysUser.getUserName());
        SysUser sysUserDb = sysUserService.getOne(userLambdaQueryWrapper,false);
        if(null!=sysUserDb&&sysUserDb.getPwd().equals(getUserPwd(sysUserDb.getPwdSalt(),sysUser.getPwd().trim()))){
            Algorithm algorithm = Algorithm.HMAC256(jwt_secret);
            String token = JWT.create()
                    .withHeader(new HashMap<>())
                    .withClaim("uid", sysUserDb.getId())
                    .withClaim("user_name", sysUserDb.getUserName())
                    .withClaim("nickname", sysUserDb.getNickname())
                    .withExpiresAt(DateUtil.date().offset(DateField.SECOND,20))
                    .sign(algorithm);
            return ApiResult.successAddData(token);
        }
        return ApiResult.error(ApiErrorCode.A0200);
    }

    @GetMapping
    public ApiResult getUserList(){
        List<SysUser> list = sysUserService.list();
        return ApiResult.successAddData(list);
    }

    @PostMapping
    public ApiResult addUser(SysUser sysUser){
        if(null==sysUser){
            return ApiResult.error(ApiErrorCode.A0400);
        }
        if(StrUtil.hasBlank(sysUser.getUserName(),sysUser.getUserName(),sysUser.getPwd())){
            return ApiResult.error(ApiErrorCode.A0402);
        }
        sysUser.setId(IdUtil.getSnowflake(1,1).nextId());
        sysUser.setPwdSalt(RandomUtil.randomString(16));
        sysUser.setPwd(getUserPwd(sysUser.getPwdSalt(),sysUser.getPwd()));
        sysUser.setCreateTime(LocalDateTime.now());
        sysUser.setUpdateTime(sysUser.getCreateTime());
        if(sysUserService.save(sysUser)){
            return ApiResult.successAddData(sysUser);
        }
        return ApiResult.error(ApiErrorCode.A0500);
    }

    private String getUserPwd(String pwdSalt,String pwd){
        return SecureUtil.md5(pwdSalt+pwd);
    }
}
